package com.example.finger;

import android.app.Activity;
import android.content.Context;
import android.os.SerialPortServiceManager;

import com.lyxmaster.lib.toasty.Toasty;

import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.ArrayList;
import java.util.List;
import java.util.Timer;
import java.util.TimerTask;
import java.util.concurrent.ExecutionException;

import android_serialport_api.SerialPort;

/**
 * Created by LYX on 2018/11/26.
 */

public class SerialPortUtil {

    String UHF_POWER_PATH = "/proc/gpiocontrol/set_uhf";

    private static SerialPortUtil INSTANCE = null;
    private SerialPort serialPort;
    private OutputStream outputStream;
    private InputStream inputStream;
    private SCMDataReceiveListener SCMDataReceiveListener;
    private List<Byte> listData = new ArrayList<>();
    private Timer timerBtRecv = new Timer();
    private TimerTask timerTaskBtRecv;

    private SerialPortUtil(){

    }

    public static SerialPortUtil getInstance(){
        if (INSTANCE == null){
            synchronized (FingerHelper.class) {
                if (INSTANCE == null)
            INSTANCE = new SerialPortUtil();
            }
        }
        return INSTANCE;
    }

    public void setSCMDataReceiveListener(SCMDataReceiveListener SCMDataReceiveListener) {
        this.SCMDataReceiveListener = SCMDataReceiveListener;
    }

    public void openSerialPort(Context context){

        if(!new Lyxkind().isKind(context)){
            ((Activity)(context)).finish();
            return;
        }

        try {

            final String portPath = "/dev/ttyMT2";
            final int baudRate = 115200;

            serialPort = new SerialPort(new File(portPath),baudRate,0);
            outputStream = serialPort.getOutputStream();
            inputStream = serialPort.getInputStream();

            new ReadThread().start();

        }catch (Exception e){
            e.printStackTrace();
            Toasty.error(context, "打开串口失败"+e.getMessage()).show();
        }

    }

    public void OpenPower(){
        gpio_control(UHF_POWER_PATH, 1);
    }

    public void ClosePower(){
        gpio_control(UHF_POWER_PATH, 0);
    }

    public void closeSerialPort(){

        try{
            inputStream.close();
            outputStream.close();
            serialPort.close();
            ClosePower();
        }catch (Exception e){
            e.printStackTrace();
        }
    }

    public void sendDataToSerialPort(byte[] data) throws Exception {
        int dataLength = data.length;
        if(dataLength > 0){
            outputStream.write(data);
            outputStream.flush();
        }
    }

    private class ReadThread extends Thread {

        @Override
        public void run() {
            super.run();
            try {
                while (true){
                    int size;
                    byte[] buffer = new byte[1024];
                    if (inputStream == null) return;
                    size = inputStream.read(buffer);
                    for(int i=0; i<size; i++){
                        listData.add(buffer[i]);
                    }
                    resetTimer();
                }
            }catch (Exception e){

            }
        }
    }

    private void resetTimer(){
        if(timerTaskBtRecv != null) timerTaskBtRecv.cancel();
        timerTaskBtRecv = new TimerTask() {
            @Override
            public void run() {
                if(SCMDataReceiveListener != null){
                    byte[] data = new byte[listData.size()];
                    for(int i=0;i<data.length; i++){
                        data[i] = listData.get(i);
                    }
                    listData.clear();
                    try {
                        SCMDataReceiveListener.dataRecevie(data);
                    }catch(Exception e) {}

                }
            }
        };
        timerBtRecv.schedule(timerTaskBtRecv, 50);
    }

    public interface SCMDataReceiveListener {
        void dataRecevie(byte[] data);
    }

    public boolean gpio_control(String path, int state) {
        if (state == 0 || state == 1) {
            try {
                FileWriter localFileWriterOn = new FileWriter(new File(path));
                if (state == 1) {
                    localFileWriterOn.write("1");
                } else if (state == 0) {
                    localFileWriterOn.write("0");
                }
                localFileWriterOn.close();
                return true;
            } catch (Exception e) {
                e.printStackTrace();
                return false;
            }
        }
        return false;
    }
}
